﻿using CasignDesignGA.Casign;
using CasignDesignGA.Casing;
using CasignDesignGA.Engine.Population.FileReader;
using CasignDesingGA.Casing;
using CasignDesignGA.Well;
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace CasignDesignGA.Engine.Population
{
    class CatalogPopulationFactory : IPopulationFactory
    {

        public CatalogPopulationFactory()
        {
            
        }
        

       

      
        public Population generatePopulation(long populationSize, double designFactor)
        {
            
            List<CasingUnit> casingTable = CasingCatalog.Instance.Catalog;
            List<ISelectable> casingCollection = new List<ISelectable>();
            Population popu = new Population();
            int nCatalogItems = casingTable.Count;
            Random randomGenerator = new Random(DateTime.Today.Millisecond);

            for (int i = 0; i < populationSize; i++)
            {
                CasingDesign aNewCasing = new CasingDesign();
                CasingUnit topCasing = null;
                CasingUnit lowCasing = null;
                
                int firstIndex = randomGenerator.Next(nCatalogItems);
                
                int secondIndex = randomGenerator.Next(nCatalogItems);

                while (firstIndex == secondIndex)
                {
                    secondIndex = randomGenerator.Next(nCatalogItems);
                }

                CasingUnit randomTopCasingUnit = casingTable[firstIndex];
                CasingUnit randomLowCasingUnit = casingTable[secondIndex];

                topCasing = randomTopCasingUnit.Clone();
                lowCasing = randomLowCasingUnit.Clone();

                long depth = Well.Well.Instance.Depth;

                long firstCasignLongitude =  Convert.ToInt64(randomGenerator.NextDouble() * depth);
                long secondCasingLongitude = depth - firstCasignLongitude;

                topCasing.Longitude = firstCasignLongitude;
                lowCasing.Longitude = secondCasingLongitude;

                aNewCasing.CasingCollection.Add(topCasing);
                aNewCasing.CasingCollection.Add(lowCasing);
                aNewCasing.LifeCycle = 0; // a New Born
                aNewCasing.calculatePrice();
                aNewCasing.calculateAptitude(designFactor);
                casingCollection.Add(aNewCasing);

            }
            popu.Individuals = casingCollection;
            return popu;
        }





        public Population generatePopulation(long populationSize)
        {
            return this.generatePopulation(populationSize, 1);
        }
    }
}
